package game;

import java.awt.Cursor;
import java.awt.Image;
import java.awt.Point;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.InputEvent;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.image.MemoryImageSource;
import java.io.BufferedReader;
import java.util.Random;
import javax.swing.JDesktopPane;
import javax.swing.JFrame;
import javax.swing.Timer;

public class Dilemma extends Game {

    double payoffMat[][] = new double[2][2];
    int choice1, choice2;
    boolean finished=false;
    String desc="";
    int totalTime=60,secs = totalTime, timeTaken=0;
    Timer time = new Timer(1000, new TimeListener());
    String state="init";
    String playerChoice[] = {"A", "B"};
    Random rand = new Random();

    /** Creates new form CoordinationGame */
    public Dilemma() {
        super();
//        super("",
//              false, //resizable
//              false, //closable
//              false, //maximizable
//              false);//iconifiable
//        javax.swing.plaf.InternalFrameUI ui = this.getUI();
//        ((javax.swing.plaf.basic.BasicInternalFrameUI)ui).setNorthPane(null);
        
        desc = "<html>If you both select A, you get "
			+ String.format ("$%.2f", payoffMat[0][0]) + ".";
        desc += "<br>If you select A and the other player selects B, you get "
			+ String.format ("$%.2f", payoffMat[0][1]) + ".";
        desc += "<br>If you select B and the other player selects A, you get "
			+ String.format ("$%.2f", payoffMat[1][0]) + ".";
        desc += "<br>If you both select B, you get "
			+ String.format ("$%.2f", payoffMat[1][1]) + ".</html>";
        // System.out.println("Desc : "+desc);
        initComponents();
        lblDesc.setText(desc);

        runner.addMouseListener(new Dilemma.CheckMouse());
        this.addMouseListener(new Dilemma.CheckMouse());

        time.start();
        int min = secs/60;
        int sec = secs%60;
        lblTime.setText(min+":"+((sec<10)?"0":"")+sec);

        hideMouse();
    }

    public Dilemma(String params, int currentRep)
    {
        super();
//        super("",
//              false, //resizable
//              false, //closable
//              false, //maximizable
//              false);//iconifiable
//        javax.swing.plaf.InternalFrameUI ui = this.getUI();
//        ((javax.swing.plaf.basic.BasicInternalFrameUI)ui).setNorthPane(null);

		String paramPart[] = params.split(",");
        payoffMat[0][0] = Double.parseDouble(paramPart[2]);
        payoffMat[0][1] = Double.parseDouble(paramPart[3]);
        payoffMat[1][0] = Double.parseDouble(paramPart[4]);
        payoffMat[1][1] = Double.parseDouble(paramPart[5]);
		this.params = params;
		repTot = Integer.parseInt (paramPart[1]);
		repNum = currentRep;

        desc = "<html>If you both select A, you get "
			+ String.format ("$%.2f", payoffMat[0][0]) + ".";
        desc += "<br>If you select A and the other player selects B, you get "
			+ String.format ("$%.2f", payoffMat[0][1]) + ".";
        desc += "<br>If you select B and the other player selects A, you get "
			+ String.format ("$%.2f", payoffMat[1][0]) + ".";
        desc += "<br>If you both select B, you get "
			+ String.format ("$%.2f", payoffMat[1][1]) + ".</html>";
        //System.out.println("Desc : "+desc);
        initComponents();
        lblDesc.setText(desc);

        runner.addMouseListener(new Dilemma.CheckMouse());
        this.addMouseListener(new Dilemma.CheckMouse());
		this.getGlassPane().addMouseListener(new Dilemma.CheckMouse());

        state="init";
        time.start();
        int min = secs/60;
        int sec = secs%60;
        lblTime.setText(min+":"+((sec<10)?"0":"")+sec);
		lblNext.setVisible (false);

        hideMouse();
    }

    private void hideMouse() {
        int[] pixels = new int[16 * 16];
        Image image = Toolkit.getDefaultToolkit().createImage(new MemoryImageSource(16, 16, pixels, 0, 16));
        Cursor transparentCursor = Toolkit.getDefaultToolkit().createCustomCursor(image, new Point(0, 0), "invisibleCursor");
        this.getGlassPane().setCursor(transparentCursor);
		this.getGlassPane().setVisible(true);
        runner.setCursor(transparentCursor);
    }

    class CheckMouse implements MouseListener{
        public void mousePressed(MouseEvent e) { hideMouse(); }
        public void mouseReleased(MouseEvent e) {}
        public void mouseEntered(MouseEvent e) {}
        public void mouseExited(MouseEvent e) {}
        public void mouseClicked(MouseEvent e) {
            int modifiers = e.getModifiers();
            if ((modifiers & InputEvent.BUTTON1_MASK) == InputEvent.BUTTON1_MASK) {
                if(state.equals("end")) {
//                    setVisible(false);
//                    g.free = true;
                }
                else {
                    chooseA();
                }
            }
            if ((modifiers & InputEvent.BUTTON2_MASK) == InputEvent.BUTTON2_MASK) {}
            if ((modifiers & InputEvent.BUTTON3_MASK) == InputEvent.BUTTON3_MASK) {
                if(state.equals("end")) {
//                    setVisible(false);
//                    g.free = true;
                }
                else {
                    chooseB();
                    secs=0;
                    state="end";
                }
            }
        }
    }


   class TimeListener implements ActionListener {
    	public void actionPerformed(ActionEvent e) {
    		secs--;
            if(secs>=0) {
                int min = secs/60;
                int sec = secs%60;
                lblTime.setText(min+":"+((sec<10)?"0":"")+sec);
            }
            if(secs==0) {
                //time.stop();
                lblA.setVisible(false);
                lblB.setVisible(false);
                lblInst.setText(null);
                lblResult.setText("Sorry, your time is up.");
				writeLog (playerId + ",,\"" + params + "\"," + repNum + ","
					+ repTot + ",TimeOut,TimeOut");
				writeGameLog (playerId + ",TimeOut,TimeOut");
                finished = true;
				totalMoneyWon += 0.0 ;
                System.out.println("G.totalMoneyWon = " + totalMoneyWon) ;
            }
            if(secs==-6) {
                time.stop();
                try {
                    setVisible(false);
                    free=true;
                } catch(Exception ex) {
                    ex.printStackTrace();
                    logError(ex);
                }
            }
    	}
    }

    public void getResult()
    {
        try {
            Random rand = new Random();
            Double decide = rand.nextDouble();

            BufferedReader br = readGameData();
            br.readLine();
            Double prob = Double.parseDouble(br.readLine());

            if(decide<=prob)
                choice2=0;
            else
                choice2=1;

            choice2 = rand.nextInt(2);
            lblResult.setText("OK");
            logResult(payoffMat[choice1][choice2],
				payoffMat[choice2][choice1]);
			
			// Translate (0,0)=1, (0,1)=2, (1,0)=3, (1,1)=4.
			int action = 2*choice1 + (int) Math.pow(2, choice2);
			int time = totalTime - secs;
			writeGameLog (playerId + "," + time + "," + action);
            secs=0;
        } catch(Exception ex) {
            ex.printStackTrace();
            logError(ex);
        }
    }

    private void logResult(double money, double oppMoney)
    {
        writeLog (playerId + ",,\"" + params + "\"," + repNum + "," + repTot
			+ "," + String.format ("$%.2f", money) + ","
			+ String.format ("$%.2f", oppMoney));
		totalMoneyWon += money ;
        System.out.println("G.totalMoneyWon = " + totalMoneyWon) ;
    }

    
    private void chooseA() {
        choice1 = 0;
        System.out.println("Choice1 set to 0");
        getResult();
        lblInst.setText(null);
        lblA.setVisible(false);
        lblB.setVisible(false);
        secs=0;
        state="end";
        finished = true;
    }
    
    private void chooseB() {
        choice1 = 1;
        System.out.println("Choice1 set to 1");
        getResult();
        lblInst.setText(null);
        lblA.setVisible(false);
        lblB.setVisible(false);
        secs=0;
        state="end";
        finished = true;
    }

    /** This method is called from within the constructor to
     * initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is
     * always regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        lblDesc = new javax.swing.JLabel();
        lblInst = new javax.swing.JLabel();
        lblResult = new javax.swing.JLabel();
        lblA = new javax.swing.JLabel();
        lblB = new javax.swing.JLabel();
        lblNext = new javax.swing.JLabel();
        lblTime = new javax.swing.JLabel();

        setBackground(new java.awt.Color(255, 255, 255));
        setBorder(null);
        setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);
        setMaximumSize(new java.awt.Dimension(800, 600));
        setPreferredSize(new java.awt.Dimension(827, 627));

        lblDesc.setFont(new java.awt.Font("Calibri", 0, 24));
        lblDesc.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
        lblDesc.setText("Instructions go here");
        lblDesc.setVerticalAlignment(javax.swing.SwingConstants.TOP);
        lblDesc.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER);

        lblInst.setFont(new java.awt.Font("Calibri", 1, 24));
        lblInst.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
        lblInst.setText("Choose A or B");
        lblInst.setAlignmentY(0.0F);
        lblInst.setHorizontalTextPosition(javax.swing.SwingConstants.CENTER);

        lblResult.setFont(new java.awt.Font("Calibri", 1, 28));
        lblResult.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);

        lblA.setIcon(new javax.swing.ImageIcon(getClass().getResource("/images/redA.png"))); // NOI18N

        lblB.setIcon(new javax.swing.ImageIcon(getClass().getResource("/images/greenB.png"))); // NOI18N

        lblNext.setIcon(new javax.swing.ImageIcon(getClass().getResource("/images/greenNext.png"))); // NOI18N

        lblTime.setFont(new java.awt.Font("Calibri", 1, 36));
        lblTime.setForeground(new java.awt.Color(153, 102, 0));
        lblTime.setIcon(new javax.swing.ImageIcon(getClass().getResource("/images/hrGlass.png"))); // NOI18N
        lblTime.setText("3:00");

        org.jdesktop.layout.GroupLayout layout = new org.jdesktop.layout.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(layout.createSequentialGroup()
                .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
                    .add(layout.createSequentialGroup()
                        .addContainerGap()
                        .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
                            .add(org.jdesktop.layout.GroupLayout.TRAILING, layout.createSequentialGroup()
                                .add(4, 4, 4)
                                .add(lblInst, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 803, Short.MAX_VALUE))
                            .add(org.jdesktop.layout.GroupLayout.TRAILING, lblResult, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 807, Short.MAX_VALUE)
                            .add(lblDesc, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 807, Short.MAX_VALUE)
                            .add(layout.createSequentialGroup()
                                .add(85, 85, 85)
                                .add(lblA)
                                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED, 169, Short.MAX_VALUE)
                                .add(lblB)
                                .add(87, 87, 87))))
                    .add(layout.createSequentialGroup()
                        .addContainerGap()
                        .add(lblTime, org.jdesktop.layout.GroupLayout.DEFAULT_SIZE, 807, Short.MAX_VALUE))
                    .add(layout.createSequentialGroup()
                        .add(292, 292, 292)
                        .add(lblNext)))
                .addContainerGap())
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
            .add(org.jdesktop.layout.GroupLayout.TRAILING, layout.createSequentialGroup()
                .add(lblTime, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 70, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED, 33, Short.MAX_VALUE)
                .add(lblDesc, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 220, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED)
                .add(lblResult, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 50, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED)
                .add(lblInst, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE, 40, org.jdesktop.layout.GroupLayout.PREFERRED_SIZE)
                .add(18, 18, 18)
                .add(layout.createParallelGroup(org.jdesktop.layout.GroupLayout.LEADING)
                    .add(lblA)
                    .add(lblB))
                .addPreferredGap(org.jdesktop.layout.LayoutStyle.RELATED)
                .add(lblNext)
                .add(28, 28, 28))
        );

        pack();
    }// </editor-fold>//GEN-END:initComponents

    /**
    * @param args the command line arguments
    */
    public static void main(String args[]) {
         try {
                    JFrame main = new JFrame();
                    JDesktopPane dPane = new JDesktopPane();
                    Dilemma frame = new Dilemma();
                    main.setSize(820, 620);
                    dPane.add(frame);
                    main.add(dPane);
                    main.setVisible(true);
                    dPane.setVisible(true);
                    frame.setSelected(true);
                    frame.setVisible(true);
                    } catch(Exception ex) {
                    ex.printStackTrace();
                    }

    }

    // Variables declaration - do not modify//GEN-BEGIN:variables
    private javax.swing.JLabel lblA;
    private javax.swing.JLabel lblB;
    private javax.swing.JLabel lblDesc;
    private javax.swing.JLabel lblInst;
    private javax.swing.JLabel lblNext;
    private javax.swing.JLabel lblResult;
    private javax.swing.JLabel lblTime;
    // End of variables declaration//GEN-END:variables

}
